package org.lee.netty.http;

import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import io.netty.handler.codec.http.*;

import java.net.URI;
import java.nio.charset.StandardCharsets;

/**
 * TestHttpServerHandler
 * http处理器
 * 1、SimpleChannelInboundHandler 是 ChannelInboundHandlerAdapter
 * 2、HttpObject 客户端和服务器端相互通讯的数据被封装成HttpObject
 *
 * @author dralee
 * @date 2022-01-03 17:46:51
 **/
public class TestHttpServerHandler extends SimpleChannelInboundHandler<HttpObject> {

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        cause.printStackTrace();
        ctx.close();
    }

    // 读取客户端数据
    @Override
    protected void channelRead0(ChannelHandlerContext ctx, HttpObject msg) throws Exception {

        System.out.println("对应channel=" + ctx.channel() + ", pipeline=" + ctx.pipeline() + ", 通过pipeline获取channel=" + ctx.pipeline().channel());
        System.out.println("当前ctx的Handler=" + ctx.handler());

        // 判断 msg是不是HttpRequest请求
        if (msg instanceof HttpRequest) {
            System.out.println("ctx:" + ctx);
            // http每次都会产生一个新的，因为用完就会释放掉
            System.out.println("pipeline hashcode=" + ctx.pipeline().hashCode() + ", TestHttpServerHandler hashcode=" + this.hashCode());
            System.out.println("msg 类型=" + msg.getClass());
            System.out.println("客户端地址" + ctx.channel().remoteAddress());

            // 获取到
            HttpRequest request = (HttpRequest) msg;
            // 获取URI
            URI uri = new URI(request.uri());
            if ("/favicon.ico".equals(uri.getPath())) {
                System.out.println("请求了favicon.ico，不做响应");
                return;
            }

            // 回复信息给浏览器[http协议]
            ByteBuf content = Unpooled.copiedBuffer("hello，这是服务器", StandardCharsets.UTF_8);
            // 构造一个http响应，即httpResponse
            FullHttpResponse resp = new DefaultFullHttpResponse(HttpVersion.HTTP_1_1, HttpResponseStatus.OK, content);
            resp.headers().set(HttpHeaderNames.CONTENT_TYPE, "text/plain;charset=utf-8");
            resp.headers().set(HttpHeaderNames.CONTENT_LENGTH, content.readableBytes());
            // 将构建好的response返回
            ctx.writeAndFlush(resp);
        }
    }
}
